//! # 库文档注释

struct Duck;
struct Pig;
/// 
/// Fly trait 只包含了一个函数签名fly，没有函数体。（可以定义默认实现）
trait Fly {
    fn fly(&self) -> bool;
}

impl Fly for Duck {
    fn fly(&self) -> bool {
        return true;
    }
}

impl Fly for Pig {
    fn fly(&self) -> bool {
        return false;
    }
}

//泛型，但进行了 trait限定（trait bound），T只能是Fly类型
fn fly_static<T: Fly>(s: T) -> bool {
    s.fly()
}

//&Fly 是一种动态类型，代表所有拥有fly这种行为的类型
fn fly_dyn(s: &Fly) -> bool {
    s.fly()
}

fn use_trait_1() {
    let pig = Pig;
    assert_eq!(fly_static::<Pig>(pig), false);
    let duck = Duck;
    assert_eq!(fly_static::<Duck>(duck), true);
    assert_eq!(fly_dyn(&Pig), false);
    assert_eq!(fly_dyn(&Duck), true);
}

use std::fmt::*;

#[derive(Debug)]
struct Point{
    x: i32,
    y: i32,
}
/*
impl Debug for Point {
    fn fmt(&self, f: &mut Formatter) -> Result {
        write!(f, "Point {{x:{}, y:{} }}", self.x, self.y)
    }
}*/
//Debug trait中定义了 fmt 函数，所以只需要为Point实现对应函数即可。
//可以使用 #[derive(Debug)] 属性，这样就自动实现了Debug trait
fn main() {
    let origin = Point{x: 0, y: 0};
    println!("The origin is: {:?}", origin);
}